package com.seal.commons.infrastructure.facade.distributed.lock;

import java.util.function.Supplier;

/**
 * ClassName:DistributedLock <br/>
 * Function: 锁的接口.  <br/>
 * Date:     2019-04-15 14:37 <br/>
 *
 * @author yong.huang
 * @see
 * @since JDK 1.8
 */
public interface DistributedLock {

    //获取锁的超时时间，单位:毫秒
    long TIMEOUT_MILLIS = 30000;

    //重试次数
    int RETRY_TIMES = Integer.MAX_VALUE;

    //间隔时间，单位：毫秒
    long SLEEP_MILLIS = 500;

    /**
     * 获取锁
     * @param key
     * @return
     */
    boolean lock(String key);

    /**
     * 获取锁，获取失败，重试${retryTimes} 次
     * @param key
     * @param retryTimes
     * @return
     */
    boolean lock(String key, int retryTimes);

    /**
     * 获取锁，获取失败，重试${retryTimes}次，每次间隔${sleepMillis} 毫秒
     * @param key
     * @param retryTimes
     * @return
     */
    boolean lock(String key, int retryTimes, long sleepMillis);

    /**
     * 获取锁并设置锁有效时间 ${expire}毫秒
     * @param key
     * @param expire
     * @return
     */
    boolean lock(String key, long expire);

    /**
     * 获取锁并设置锁有效时间 ${expire}毫秒，获取失败，重试${retryTimes} 次
     * @param key
     * @param expire
     * @return
     */
    boolean lock(String key, long expire, int retryTimes);


    /**
     * 获取锁并设置锁有效时间 ${expire}毫秒，获取失败，重试${retryTimes} 次, 每次间隔${sleepMillis} 毫秒
     * @param key
     * @param expire
     * @return
     */
    boolean lock(String key, long expire, int retryTimes, long sleepMillis);

    /**
     * 释放锁
     * @param key
     * @return
     */
    boolean releaseLock(String key);

    /**
     * 获取锁，并回调
     * @param key
     * @param supplier
     * @param <T>
     * @return
     */
    <T> T acquire(String key, Supplier<T> supplier);

    <T> T acquire(String key, long expire, Supplier<T> supplier);

    <T> T acquire(String key, long expire, int retryTimes, Supplier<T> supplier);

    <T> T acquire(String key, long expire, int retryTimes, long sleepMillis, Supplier<T> supplier);


}
